package com.zmn.oms.dubbo.impl.zmn.master.order;

import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;
import com.github.ltsopensource.core.domain.Job;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.zmn.base.engineer.common.dro.foreign.engineer.ForeignEngineerDetailInfoDRO;
import com.zmn.base.engineer.dubbo.interfaces.foreign.EngineerListRemoteService;
import com.zmn.base.product.common.consts.BaseProductConsts;
import com.zmn.base.product.common.dto.product.ProductBaseQuery;
import com.zmn.base.product.common.dto.product.ec.ProductBaseDRO;
import com.zmn.base.product.dubbo.interfaces.product.foreign.ProductForeignListRemoteService;
import com.zmn.cds.httpcall.CdsHttpCallClient;
import com.zmn.cds.httpcall.CdsHttpCallResult;
import com.zmn.cds.httpcall.biz.custom_invocation.CustomInvocationDIO;
import com.zmn.cds.httpcall.biz.orderclue.QueryOrderClueDIO;
import com.zmn.cds.httpcall.biz.orderclue.QueryOrderClueDRO;
import com.zmn.common.dto2.ResponseDTO;
import com.zmn.common.utils.date.DateUtil;
import com.zmn.common.utils.number.NumberUtil;
import com.zmn.common.utils.reflect.BeanMapper;
import com.zmn.common.utils.string.StringUtil;
import com.zmn.consts.GlobalConsts;
import com.zmn.manager.lts.interfaces.task.TaskManager;
import com.zmn.manager.redis.RedisManager;
import com.zmn.oms.business.interfaces.messageV1.SendOrderMessageService;
import com.zmn.oms.business.interfaces.messageV1.app.MessageSendAppService;
import com.zmn.oms.business.interfaces.messageV1.common.MessageGetSendInfoService;
import com.zmn.oms.business.interfaces.messageV1.text.MessageSendTextService;
import com.zmn.oms.business.interfaces.messageV1.wechat.MessageWeChatTemplateService;
import com.zmn.oms.business.interfaces.mq.MqProviderService;
import com.zmn.oms.business.interfaces.order.OrderExtendBService;
import com.zmn.oms.business.interfaces.track.OrderTrackBService;
import com.zmn.oms.business.interfaces.work.OrderWorkProgrammeBService;
import com.zmn.oms.business.interfaces.work.masterwork.MasterWorkBService;
import com.zmn.oms.business.interfaces.xno.OrderXnoBindService;
import com.zmn.oms.common.constant.*;
import com.zmn.oms.common.dio.attachment.ModifyOrderWorkAttachmentDIO;
import com.zmn.oms.common.dio.normal.pay.WaitPayDIO;
import com.zmn.oms.common.dro.PayChannelDRO;
import com.zmn.oms.common.dto.ResultDTO;
import com.zmn.oms.common.exception.OmsBaseException;
import com.zmn.oms.dubbo.dto.common.SimpleResultDRO;
import com.zmn.oms.dubbo.dto.common.work.ServiceCompleteDIO;
import com.zmn.oms.dubbo.dto.common.work.*;
import com.zmn.oms.dubbo.impl.OmsBaseRemoteService;
import com.zmn.oms.dubbo.interfaces.zmn.master.order.MasterWorkRemoteService;
import com.zmn.oms.dubbo.utils.DubboConsts;
import com.zmn.oms.manager.utils.TaskConsts;
import com.zmn.oms.model.dto.OrderExtendDTO;
import com.zmn.oms.model.dto.serviceitem.AddOrderServiceItemDTO;
import com.zmn.oms.model.dto.work.masterwork.*;
import com.zmn.oms.model.dto.work.modify.OrderWarrantyDTO;
import com.zmn.oms.model.dto.work.modify.amount.ZsDiscountDTO;
import com.zmn.oms.model.dto.work.modify.amount.ZsUpdatePriceDTO;
import com.zmn.oms.model.entity.detail.OrderDetail;
import com.zmn.oms.model.entity.masterworking.MasterWorking;
import com.zmn.oms.model.entity.member.OrderMember;
import com.zmn.oms.model.entity.order.OrderExtend;
import com.zmn.oms.model.entity.orderappbind.OrderThirdAppBind;
import com.zmn.oms.model.entity.orderattachment.OrderAttachment;
import com.zmn.oms.model.entity.orderfinalpricequotation.OrderFinalPriceQuotation;
import com.zmn.oms.model.entity.orderfinalpricequotation.OrderFinalPriceQuotationQuery;
import com.zmn.oms.model.entity.pay.OrderPay;
import com.zmn.oms.model.entity.track.OrderTrack;
import com.zmn.oms.model.entity.work.OrderWork;
import com.zmn.oms.model.entity.work.OrderWorkQuery;
import com.zmn.oms.model.vo.work.OperatePermissionVO;
import com.zmn.oms.model.vo.work.detail.ZsXnoBindVO;
import com.zmn.oms.services.interfaces.detail.OrderDetailService;
import com.zmn.oms.services.interfaces.masterworking.MasterWorkingService;
import com.zmn.oms.services.interfaces.member.OrderMemberService;
import com.zmn.oms.services.interfaces.order.OrderExtendService;
import com.zmn.oms.services.interfaces.orderattachment.OrderAttachmentService;
import com.zmn.oms.services.interfaces.orderfinalpricequotation.OrderFinalPriceQuotationService;
import com.zmn.oms.services.interfaces.pay.OrderPayService;
import com.zmn.oms.services.interfaces.track.OrderTrackService;
import com.zmn.oms.services.interfaces.visit.OrderVisitService;
import com.zmn.oms.services.interfaces.work.OrderWorkService;
import com.zmn.oms.services.interfaces.work.masterwork.MasterWorkService;
import com.zmn.oms.third.zhimi.ZhimiConsts;
import com.zmn.oms.third.zhimi.service.ZhimiOrderExtendService;
import com.zmn.oms.zmn.business.interfaces.orderpay.OrderPayChannelBService;
import com.zmn.oms.zmn.business.interfaces.work.OrderWorkModifyProductBService;
import com.zmn.oms.zmn.business.interfaces.work.ZsOrderWorkBService;
import com.zmn.oms.zmn.business.interfaces.work.ZsOrderWorkOperatePermissionBService;
import com.zmn.oms.zmn.business.interfaces.work.ZsOrderWorkQueryBService;
import com.zmn.oms.zmn.business.interfaces.work.autoflow.WorkFlowContextBService;
import com.zmn.oms.zmn.business.interfaces.work.masterwork.ZsMasterWorkBService;
import com.zmn.oms.zmn.normal.business.interfaces.serviceitem.ZsNormalOrderServiceItemBService;
import com.zmn.oms.zmn.normal.business.interfaces.work.masterwork.ZsNormalMasterWorkBService;
import com.zmn.pay.common.constant.PayConsts;
import com.zmn.track.dubbo.interfaces.trackwork.TrackWorkModifyRemoteService;
import com.zmn.uuc.dubbo.interfaces.user.UserThirdListRemoteService;
import com.zmn.vas.common.dio.order.OrderExtensionDIO;
import com.zmn.vas.common.dro.order.ExtendedWarrantyDRO;
import com.zmn.vas.dubbo.consts.VasDubboConsts;
import com.zmn.vas.dubbo.interfaces.order.VasOrderListRemoteService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.dubbo.config.annotation.Reference;
import org.apache.dubbo.config.annotation.Service;
import org.springframework.beans.factory.annotation.Autowired;

import javax.annotation.Resource;
import javax.validation.constraints.NotNull;
import java.util.*;
import java.util.stream.Collectors;

/**
 * 类描述：师傅工单服务
 *
 * @author heciqi
 * @date 2020/03/27 13:47
 */
@Slf4j
@Service(loadbalance = "roundrobin", timeout = 20000, retries = 2, version = DubboConsts.INTERFACE_VERSION)
public class MasterWorkRemoteServiceImpl extends OmsBaseRemoteService implements MasterWorkRemoteService {
	private static final String TAG = "啄木鸟-普通工单-工程师工单dubbo接口";

	@Reference(version = VasDubboConsts.INTERFACE_VERSION, check = false)
	private VasOrderListRemoteService vasOrderListRemoteService;

	@Autowired
	private OrderWorkService orderWorkService;
	@Autowired
	private ZsMasterWorkBService zsMasterWorkBService;
	@Autowired
	private MasterWorkBService masterWorkBService;
	@Autowired
	private MasterWorkService masterWorkService;
	@Autowired
	private MasterWorkingService masterWorkingService;
	@Autowired
	private ZsOrderWorkBService zsOrderWorkBService;
	@Autowired
	private OrderXnoBindService orderXnoBindService;
	@Autowired
	OrderVisitService orderVisitService;
	@Autowired
	private ZsNormalMasterWorkBService zsNormalMasterWorkBService;
	@Autowired
	private OrderWorkModifyProductBService orderWorkModifyProductBService;
	@Autowired
	private SendOrderMessageService sendOrderMessageService;
	@Autowired
	private OrderDetailService orderDetailService;
	@Autowired
	private OrderMemberService orderMemberService;
	@Autowired
	private OrderTrackService orderTrackService;
	@Autowired
	private ZsOrderWorkQueryBService zsOrderWorkQueryBService;
	@Autowired
	private ZhimiOrderExtendService zhimiOrderExtendService;
	@Autowired
	private WorkFlowContextBService workFlowContextBService;
	@Autowired
	private OrderAttachmentService orderAttachmentService;
	@Autowired
	private OrderExtendService orderExtendService;
	@Autowired
	private TaskManager taskManager;
	@Autowired
	private RedisManager redisManager;
	@Autowired
	private OrderTrackBService orderTrackBService;
	@Autowired
	private OrderExtendBService orderExtendBService;
	@Autowired
	private MessageWeChatTemplateService messageWeChatTemplateService;
	@Autowired
	private OrderWorkProgrammeBService orderWorkProgrammeBService;
	@Autowired
	private MessageSendAppService messageSendAppService;
	@Autowired
	private MessageSendTextService messageSendTextService;
	@Autowired
	private OrderPayChannelBService orderPayChannelBService;
	@Autowired
	private ZsOrderWorkOperatePermissionBService orderWorkOperatePermissionBService;
    @Autowired
	protected MessageGetSendInfoService messageGetSendInfoService;

	@Autowired
	private ZsNormalOrderServiceItemBService zsNormalOrderServiceItemBService;

	@Reference(version = com.zmn.base.engineer.common.constants.DubboConsts.INTERFACE_VERSION, check = false)
	private EngineerListRemoteService engineerListRemoteService;

	//@Reference(version = com.zmn.base.engineer.common.constants.DubboConsts.INTERFACE_VERSION, check = false)
	//private EngineerTouchModifyRemoteService engineerTouchModifyRemoteService;

	@Autowired
	private MqProviderService mqProviderService;

	@Reference(version = com.zmn.track.dubbo.consts.DubboConsts.INTERFACE_VERSION, check = false)
	private TrackWorkModifyRemoteService trackWorkModifyRemoteService;
	@Autowired
	protected OrderPayService orderPayService;

	@Resource
	private OrderFinalPriceQuotationService orderFinalPriceQuotationService;

	@DubboReference(version = com.zmn.uuc.common.constant.DubboConsts.INTERFACE_VERSION,check = false)
	private UserThirdListRemoteService userThirdListRemoteService;

	@DubboReference(version = com.zmn.base.plat.engine.common.constant.DubboConsts.INTERFACE_VERSION,check = false)
	private ProductForeignListRemoteService productForeignListRemoteService;

	/**
	 * 工程师接单
	 * @param masterTakeDIO
	 */
	@Override
	public ResponseDTO<WorkListDRO> takeOrder(MasterTakeDIO masterTakeDIO) {
		try {
			MasterTakeDTO masterTakeDTO = BeanMapper.map(masterTakeDIO, MasterTakeDTO.class);
			super.setLogParam(masterTakeDIO, masterTakeDTO);
			zsMasterWorkBService.updateMasterTake(masterTakeDTO);

			// 返回更新后的工单列表
			WorkListDTO workListDTO = zsMasterWorkBService.getWorkingList(masterTakeDIO.getMasterId());
			WorkListDRO workListDRO = BeanMapper.map(workListDTO, WorkListDRO.class);
			return ResponseDTO.success(workListDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 联系用户
	 *
	 * @param contactUserDIO
	 * @return
	 */
	@Override
	public ResponseDTO contactUser(ContactUserDIO contactUserDIO) {
		try {
			ContactUserDTO contactUserDTO = BeanMapper.map(contactUserDIO, ContactUserDTO.class);
			this.setLogParam(contactUserDIO, contactUserDTO);
			zsMasterWorkBService.saveContactUser(contactUserDTO);
			return ResponseDTO.success();
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 工程师出发
	 *
	 * @param masterLeaveDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyMasterLeave(MasterLeaveDIO masterLeaveDIO) {
		try {
			MasterLeaveDTO levaeDTO = BeanMapper.map(masterLeaveDIO, MasterLeaveDTO.class);
			this.setLogParam(masterLeaveDIO, levaeDTO);
			levaeDTO.setSessionId(masterLeaveDIO.getSessionId());

			WorkDetailDTO workDetailDTO = zsMasterWorkBService.updateMasterLeave(levaeDTO);

			WorkDetailDRO detailDRO = BeanMapper.map(workDetailDTO, WorkDetailDRO.class);

			return ResponseDTO.success(detailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 上门服务
	 *
	 * @param masterVisitDIO
	 */
	@Override
	public ResponseDTO<MasterVisitResponseDRO> visitServ(MasterVisitDIO masterVisitDIO) {
		MasterVisitDTO visitDTO = BeanMapper.map(masterVisitDIO, MasterVisitDTO.class);
		this.setLogParam(masterVisitDIO, visitDTO);

		try {
			MasterVisitResponseDTO visitResponseDTO = zsMasterWorkBService.updateMasterVisit(visitDTO);
			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(masterVisitDIO.getPlat(),
					masterVisitDIO.getOrderId(), masterVisitDIO.getWorkId(), masterVisitDIO.getMasterId(),
					masterVisitDIO.getAgent());
			visitResponseDTO.setWorkDetail(workDetail);
			// 返回更新后的工单列表
			WorkListDTO workListDTO = zsMasterWorkBService.getWorkingList(masterVisitDIO.getMasterId());
			visitResponseDTO.setWorkList(workListDTO);
			MasterVisitResponseDRO masterVisitResponseDRO = BeanMapper.map(visitResponseDTO, MasterVisitResponseDRO.class);
			return ResponseDTO.success(masterVisitResponseDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 完成工单
	 *
	 * @param completeOrderDIO
	 */
	@Override
	public ResponseDTO<WorkListDRO> completeOrder(CompleteOrderDIO completeOrderDIO) {
		try {
			CompleteDTO completeDTO = BeanMapper.map(completeOrderDIO, CompleteDTO.class);
			this.setLogParam(completeOrderDIO, completeDTO);

			List<OrderPay> orderPays = orderPayService.listOrderPayByOrderId(completeDTO.getOrderId());
			Integer warrantyPaymentAmount = orderPays.stream()
					.filter(x -> Objects.equals(x.getAmountType(), OrderPayConsts.ORDER_PAY_MASTER)
							&& Objects.equals(PayConsts.PAY_TRADE_TYPE_INTIME, x.getTradeType())
							&& Objects.equals(PayConsts.PAY_CHANNEL_PLATFORM_DEPOSIT, x.getPayChannelId()))
					.mapToInt(OrderPay::getAmount).sum();

			log.info("判断是否是通过质保金支付{},{}",completeDTO.getOrderId(),warrantyPaymentAmount);
			if (NumberUtil.isNotNullOrZero(warrantyPaymentAmount)) {
				return ResponseDTO.fail("质保金支付订单，不可完成");
			}
			// 检测完成
			zsNormalMasterWorkBService.checkComplete(completeDTO);

			Integer channelId = completeDTO.getChannelId();


			if (channelId == null) {
				OrderWork orderWork = orderWorkService.findOrderWorkByKey(completeDTO.getOrderId(), completeDTO.getWorkId());
				if (orderWork == null) {
					throw new OmsBaseException("工单不存在");
				}
				channelId = orderWork.getChannelId();
			}

			// 智米订单在完成前，需先同步给对方完成状态
			if (Objects.equals(ZhimiConsts.CHANNEL_ID, channelId)) {
				ResultDTO resultDTO = zhimiOrderExtendService.check4Complete(completeDTO.getOrderId());
				if (!resultDTO.isStatusBool()) {
					throw new OmsBaseException(resultDTO.getMessage());
				}
			}

			// TODO -lhl 临时处理，待优化：万科需用户确认后，才能完成，不然不给结算 2022.08.04 by lhl
			if (Objects.equals(ChannelConsts.CHANNEL_ID_WANKE, channelId)) {
				log.debug("【万科幸福社orderWorkService.findOrderWorkByKey的入参，orderId:{}, workId:{}", completeDTO.getOrderId(),
						completeDTO.getWorkId());
				OrderWork orderWork = orderWorkService.findOrderWorkByKey(completeDTO.getOrderId(), completeDTO.getWorkId());
				log.debug("【万科幸福社】orderWorkService.findOrderWorkByKey的响应:{}", JSONObject.toJSONString(orderWork));

				// 订单类型：1 新单、2 返修单、3 退款单
				Integer orderType = orderWork.getType();
				log.info("【万科幸福社】订单【{}】服务完成orderType:{}", completeDTO.getOrderId(), orderType);
				if(!Objects.equals(orderType,2)){
					// 返修单不走这个逻辑
					try {
						// userConfirm 的值：1-否；2-是；为null时，表示未给渠道同步用户确认请求
						String userConfirm = null;

						// 创建 CdsHttpCallClient 对象
						CdsHttpCallClient client = CdsHttpCallClient.newInstance(
								CdsConsts.HttpCall.BASE_URL,
								CdsConsts.HttpCall.MODEL_NAME,
								CdsConsts.HttpCall.SECRET_KEY
						);
						// 封装请求参数
						QueryOrderClueDIO dio = new QueryOrderClueDIO();
						dio.setZmnOrderId(completeDTO.getWorkId());
						// 获取渠道订单线索
						CdsHttpCallResult<QueryOrderClueDRO> result = client.queryOrderClue(dio);
						String extendDataStr = Optional.ofNullable(result.getData())
								.map(QueryOrderClueDRO::getOrderClueExtendData)
								.orElse(null);
						if (StringUtil.isNotBlank(extendDataStr)) {
							HashMap<String, String> extendDataMap = JSON.parseObject(
									extendDataStr,
									new TypeReference<HashMap<String, String>>() {
									}
							);

							// userConfirm 的值：1-否；2-是；为null时，表示未给渠道同步用户确认请求
							userConfirm = extendDataMap.get("userConfirm");
						}

						if(userConfirm != null && "0".equals(userConfirm.trim())){

							// 已经通知万科服务完成，用户未确认
							throw new OmsBaseException("已发送用户确认消息，请引导用户确认后再试");
						}

						// 订单类型为新单且用户未确认
						if (userConfirm == null || !"2".equals(userConfirm.trim())) {
							// 调用发送用户确认接口
							CustomInvocationDIO customInvocationDIO = new CustomInvocationDIO();
							customInvocationDIO.setZmnOrderId(completeDTO.getWorkId());
							customInvocationDIO.setCustomFun("merchant_confirm");
							customInvocationDIO.setFunName("服务完成");
							CdsHttpCallResult customInvocationResult = client.customInvocation(customInvocationDIO);
							if (customInvocationResult.isStatusBool()) {
								throw new OmsBaseException("已发送用户确认消息，请引导用户确认后再试");
							}
							else {
								throw new OmsBaseException(String.format("无法完成服务: %s", customInvocationResult.getMessage()));
							}
						}
					} catch (Exception e) {
						log.error(String.format("【万科幸福社】 订单[%s]操做服务完成失败: %s", completeDTO.getWorkId(), e.getMessage()), e);
						throw (e instanceof OmsBaseException) ? (OmsBaseException)e : new OmsBaseException("系统错误，无法完成服务");
					}
				}

			}

			// 完成
			zsNormalMasterWorkBService.completeOrder(completeDTO);

			// 发送消息
			orderWorkProgrammeBService.sendOperateInfo(completeDTO.getOrderId(), AppConsts.OPERATE_TYPE_COMPLETE);

			workFlowContextBService.asyncAutoFlow(completeOrderDIO.getOrderId(), completeDTO.getWorkId());

			// 返回更新后的工单列表
			WorkListDTO workListDTO = zsMasterWorkBService.getWorkingList(completeOrderDIO.getMasterId());
			WorkListDRO workListDRO = BeanMapper.map(workListDTO, WorkListDRO.class);
			return ResponseDTO.success(workListDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 改价格
	 *
	 * @param changePriceDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyPrice(ChangePriceDIO changePriceDIO) {
		try {
			ChangePriceDTO changePriceDTO = BeanMapper.map(changePriceDIO, ChangePriceDTO.class);
			super.setLogParam(changePriceDIO, changePriceDTO);

			zsMasterWorkBService.updatePrice(changePriceDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(changePriceDIO.getPlat(),
					changePriceDIO.getOrderId(), changePriceDIO.getWorkId(), changePriceDIO.getMasterId(),
					changePriceDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 优惠
	 *
	 * @param procDiscountDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> procDiscount(ProcDiscountDIO procDiscountDIO) {
		logger.info("工程师修改优惠procDiscount入参={}", JSON.toJSONString(procDiscountDIO));
		OrderWork orderWork = orderWorkService.findOrderWorkByKey(procDiscountDIO.getOrderId(), procDiscountDIO.getWorkId());
		if (orderWork.getStatus() >= OrderStatusConsts.WORK_STATUS_COMPLETE) {
			ResponseDTO.fail(OrderFailConsts.FAIL_DATA_CHANGE_ORDER_STATUS, "完成后不可操作优惠");
		}
		if (!Objects.equals(orderWork.getMasterId(), procDiscountDIO.getMasterId())) {
			return ResponseDTO.fail(OrderFailConsts.FAIL_DATA_CHANGE_ORDER_NOMASTER, "工单已被处理");
		}

		ZsDiscountDTO discountDTO = new ZsDiscountDTO();
		discountDTO.setOperatorRemark(procDiscountDIO.getDiscountRemark());
		this.setLogParam(procDiscountDIO, discountDTO);
		discountDTO.setDiscountAmount(procDiscountDIO.getDiscountAmount());
		discountDTO.setOperateId(OrderConsts.ORDER_OP_TYPE_DISCOUNT_LEVEL_ONE);
		discountDTO.setMasterId(procDiscountDIO.getMasterId());
/*		// 计价器工单 & 非言而有信子公司 9 折，其他情况6折
		if (Objects.equals(orderWork.getServItemType(), OrderConsts.SERVICE_ITEM_TYPE_FAULT) && !Objects.equals(CompanyConsts.ZMN_YEYX_COMPANY_ID, orderWork.getCompanyId())) {
			discountDTO.setOperateId(OrderConsts.ORDER_OP_TYPE_DISCOUNT_LEVEL_THREE);
		} else {
			discountDTO.setOperateId(OrderConsts.ORDER_OP_TYPE_DISCOUNT_LEVEL_ONE);
		}*/

		try {
			// 申请优惠需10-20随机秒审核，定时后自动保存
			if (Objects.equals(procDiscountDIO.getApplyDiscountFlag(), GlobalConsts.YES)) {
				addMasterApplyDiscountJob(discountDTO);
			} else {
				zsMasterWorkBService.saveDiscount(discountDTO);
			}
			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(procDiscountDIO.getPlat(),
					procDiscountDIO.getOrderId(), procDiscountDIO.getWorkId(), procDiscountDIO.getMasterId(),
					procDiscountDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 纸质保修卡
	 *
	 * @param manualCodeDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyManualCode(ManualCodeDIO manualCodeDIO) {
		try {
			ManualCodeDTO manualCodeDTO = BeanMapper.map(manualCodeDIO, ManualCodeDTO.class);
			this.setLogParam(manualCodeDIO, manualCodeDTO);

			zsMasterWorkBService.updateManualCode(manualCodeDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(manualCodeDIO.getPlat(),
					manualCodeDIO.getOrderId(), manualCodeDIO.getWorkId(), manualCodeDIO.getMasterId(),
					manualCodeDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 工程师备注
	 *
	 * @param masterRemarkDIO
	 */
	@Override
	public ResponseDTO<MasterRemarkResponseDRO> modifyMasterRemark(MasterRemarkDIO masterRemarkDIO) {
		try {
			List<OrderTrack> orderTrackList = orderTrackService.listOrderTrackByWorkIdSrcMaster(masterRemarkDIO.getOrderId(), masterRemarkDIO.getWorkId());
			// 过滤未完成跟单项
			orderTrackList = orderTrackList.stream().filter(track -> Objects.equals(track.getComplete(), GlobalConsts.NO)).collect(Collectors.toList());
			if (!orderTrackList.isEmpty() && !masterRemarkDIO.getWorkTrackList().isEmpty()) {
				Set<Integer> orderTrackSet = orderTrackList.stream().map(OrderTrack::getMapId).collect(Collectors.toSet());
				Optional<WorkTrackDIO> workTrackDIO = masterRemarkDIO.getWorkTrackList().stream().filter(x -> orderTrackSet.contains(x.getMapId())).findAny();
				// 后台完成或删除了该跟单项的备注，该订单在APP端又可以发起此跟单项
				if (workTrackDIO.isPresent()) {
					return ResponseDTO.fail(OrderFailConsts.FAIL_CONFIG, "请勿重复提交跟单项");
				}
			}
			MasterRemarkDTO masterRemarkDTO = BeanMapper.map(masterRemarkDIO, MasterRemarkDTO.class);
			this.setLogParam(masterRemarkDIO, masterRemarkDTO);
			logger.info("工程师修改备注：start");
			boolean refreshWorkList = zsMasterWorkBService.updateMasterRemark(masterRemarkDTO);
			logger.info("工程师修改备注：end");
			MasterRemarkResponseDRO masterRemarkResponseDRO = new MasterRemarkResponseDRO();

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(masterRemarkDIO.getPlat(),
					masterRemarkDIO.getOrderId(), masterRemarkDIO.getWorkId(), masterRemarkDIO.getMasterId(),
					masterRemarkDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			masterRemarkResponseDRO.setWorkDetail(workDetailDRO);

			// 工单列表需要刷新
			if (refreshWorkList) {
				// 返回更新后的工单列表
				WorkListDTO workListDTO = zsMasterWorkBService.getWorkingList(masterRemarkDIO.getMasterId());
				WorkListDRO workListDRO = BeanMapper.map(workListDTO, WorkListDRO.class);
				masterRemarkResponseDRO.setWorkList(workListDRO);
			}

			return ResponseDTO.success(masterRemarkResponseDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 保修项
	 *
	 * @param procWarrantyDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyWarranty(ProcWarrantyDIO procWarrantyDIO) {
		logger.info("订单号{} 保存保修项入参{}", procWarrantyDIO.getOrderId(), procWarrantyDIO);
		try {
			OrderWarrantyDTO orderWarrantyDTO = BeanMapper.map(procWarrantyDIO, OrderWarrantyDTO.class);
			super.setLogParam(procWarrantyDIO, orderWarrantyDTO);

			zsMasterWorkBService.updateWarranty(orderWarrantyDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(procWarrantyDIO.getPlat(),
					procWarrantyDIO.getOrderId(), procWarrantyDIO.getWorkId(), procWarrantyDIO.getMasterId(),
					procWarrantyDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 服务项
	 *
	 * @param procServiceItemDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyServiceItem(ProcServiceItemDIO procServiceItemDIO) {
		try {
			log.info("工程师修改服务项入参：{}", JSON.toJSONString(procServiceItemDIO));
			AddOrderServiceItemDTO addOrderServiceItemDTO = BeanMapper.map(procServiceItemDIO, AddOrderServiceItemDTO.class);
			addOrderServiceItemDTO.setQuotationType(GlobalConsts.OPERATE_USER_TYPE_MASTER);
			this.setLogParam(procServiceItemDIO, addOrderServiceItemDTO);
			zsMasterWorkBService.updateServiceItem(addOrderServiceItemDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(procServiceItemDIO.getPlat(),
					procServiceItemDIO.getOrderId(), procServiceItemDIO.getWorkId(), procServiceItemDIO.getMasterId(),
					procServiceItemDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);

			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	@Override
	public ResponseDTO<Integer> getDiscount(ProcServiceItemDIO procServiceItemDIO) {
		try {
 			log.info("获取优惠价入参：{}", JSON.toJSONString(procServiceItemDIO));
			AddOrderServiceItemDTO addOrderServiceItemDTO = BeanMapper.map(procServiceItemDIO, AddOrderServiceItemDTO.class);
			addOrderServiceItemDTO.setQuotationType(GlobalConsts.OPERATE_USER_TYPE_MASTER);
			Integer discount = zsNormalOrderServiceItemBService.getDiscount(addOrderServiceItemDTO);
			return ResponseDTO.success(discount);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 贴花照片
	 *
	 * @param orderImageDIO
	 */
	@Override
	public ResponseDTO modifyAppliqueImage(OrderImageDIO orderImageDIO) {
		try {
			OrderImageDTO orderImageDTO = BeanMapper.map(orderImageDIO, OrderImageDTO.class);
			super.setLogParam(orderImageDIO, orderImageDTO);

			zsMasterWorkBService.updateAppliqueImage(orderImageDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(orderImageDIO.getPlat(),
					orderImageDIO.getOrderId(), orderImageDIO.getWorkId(), orderImageDIO.getMasterId(),
					orderImageDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 工单照片
	 *
	 * @param orderImageDIO
	 */
	@Override
	public ResponseDTO modifyOrderImage(OrderImageDIO orderImageDIO) {
		try {
			OrderImageDTO orderImageDTO = BeanMapper.map(orderImageDIO, OrderImageDTO.class);
			super.setLogParam(orderImageDIO, orderImageDTO);
			zsMasterWorkBService.updateOrderImage(orderImageDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(orderImageDIO.getPlat(),
					orderImageDIO.getOrderId(), orderImageDIO.getWorkId(), orderImageDIO.getMasterId(),
					orderImageDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 工单工程师照片
	 *
	 * @param orderImageDIO
	 */
	@Override
	public ResponseDTO modifyMasterImage(OrderImageDIO orderImageDIO) {
		try {
			OrderImageDTO orderImageDTO = BeanMapper.map(orderImageDIO, OrderImageDTO.class);
			super.setLogParam(orderImageDIO, orderImageDTO);

			zsMasterWorkBService.updateMasterImage(orderImageDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(orderImageDIO.getPlat(),
					orderImageDIO.getOrderId(), orderImageDIO.getWorkId(), orderImageDIO.getMasterId(),
					orderImageDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 检查工程师是否有进行中工单
	 *
	 * @param checkMasterWorkStatusDIO
	 */
	@Override
	public ResponseDTO<Boolean> checkMasterWorkStatus(CheckMasterWorkStatusDIO checkMasterWorkStatusDIO) {
		try {
			boolean ret = zsMasterWorkBService.checkWorkStatus(checkMasterWorkStatusDIO.getMasterId(), checkMasterWorkStatusDIO.getStartTime(), checkMasterWorkStatusDIO.getEndTime());
			return ResponseDTO.success(ret);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 检查工程师是否有进行中工单 (区分返回)
	 *
	 * @param checkMasterWorkStatusDIO
	 */
	@Override
	public ResponseDTO<MasterWorkStatusDRO> getMasterWorkStatus(CheckMasterWorkStatusDIO checkMasterWorkStatusDIO){
		try {
			MasterWorkStatusDTO masterWorkStatus = zsMasterWorkBService.getMasterWorkStatus(checkMasterWorkStatusDIO.getMasterId(), checkMasterWorkStatusDIO.getStartTime(), checkMasterWorkStatusDIO.getEndTime());
			log.info("getMasterWorkStatus dio:{} ,dro:{}", checkMasterWorkStatusDIO, JSON.toJSONString(masterWorkStatus));
			return ResponseDTO.success(BeanMapper.map(masterWorkStatus, MasterWorkStatusDRO.class));
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	};

	/**
	 * 检查工单优惠状态
	 *
	 * @param masterWorkDIO
	 */
	@Override
	public ResponseDTO checkDiscountStatus(MasterWorkDIO masterWorkDIO) {
		try {
			zsMasterWorkBService.checkDiscountStatus(masterWorkDIO.getOrderId(), masterWorkDIO.getWorkId(),
					masterWorkDIO.getMasterId());
			return ResponseDTO.success();
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 检查修改预约时间
	 *
	 * @param modifyDutyTimeDIO
	 */
	@Override
	public ResponseDTO<SimpleResultDRO> checkModifyDutyTime(ModifyDutyTimeDIO modifyDutyTimeDIO) {
		try {
			ModifyDutyTimeDTO modifyDutyTimeDTO = BeanMapper.map(modifyDutyTimeDIO, ModifyDutyTimeDTO.class);

			com.zmn.oms.common.dto.ResultDTO<Integer> resultDTO = zsMasterWorkBService.checkDutyTimeCount(modifyDutyTimeDTO);
			SimpleResultDRO simpleResultDRO = new SimpleResultDRO();
			simpleResultDRO.setValue(resultDTO.getData());
			simpleResultDRO.setComment(resultDTO.getMessage());

			return ResponseDTO.success(simpleResultDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 修改预约时间
	 *
	 * @param modifyDutyTimeDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyDutyTime(ModifyDutyTimeDIO modifyDutyTimeDIO) {
		try {
			ModifyDutyTimeDTO modifyDutyTimeDTO = BeanMapper.map(modifyDutyTimeDIO, ModifyDutyTimeDTO.class);
			this.setLogParam(modifyDutyTimeDIO, modifyDutyTimeDTO);

			zsMasterWorkBService.updateDutyTime(modifyDutyTimeDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(modifyDutyTimeDIO.getPlat(),
					modifyDutyTimeDIO.getOrderId(), modifyDutyTimeDIO.getWorkId(), modifyDutyTimeDIO.getMasterId(),
					modifyDutyTimeDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);

			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}
	/**
	 * 修改预约时间 （不修改库存）
	 *
	 * @param modifyDutyTimeDIO
	 */
	@Override
	public ResponseDTO modifyDutyTimeWithNoStock(ModifyDutyTimeDIO modifyDutyTimeDIO) {
		try {
			ModifyDutyTimeDTO modifyDutyTimeDTO = BeanMapper.map(modifyDutyTimeDIO, ModifyDutyTimeDTO.class);
			this.setLogParam(modifyDutyTimeDIO, modifyDutyTimeDTO);

			zsMasterWorkBService.updateDutyTimeWithNoStock(modifyDutyTimeDTO);

			return ResponseDTO.success();
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 改派工程师
	 *
	 * @param changeMasterDIO
	 */
	@Override
	public ResponseDTO<WorkListDRO> modifyDistributeMaster(ChangeMasterDIO changeMasterDIO) {
		try {
			OrderWork orderWork = orderWorkService.findOrderWorkByKey(changeMasterDIO.getOrderId(), changeMasterDIO.getWorkId());
			if (orderWork.getStatus() >= OrderStatusConsts.WORK_STATUS_COMPLETE) {
				return ResponseDTO.fail(OrderFailConsts.FAIL_DATA_CHANGE_ORDER_STATUS, "完成后不可转派");
			}
			if (!Objects.equals(orderWork.getMasterId(), changeMasterDIO.getMasterId())) {
				return ResponseDTO.fail(OrderFailConsts.FAIL_DATA_CHANGE_ORDER_NOMASTER, "工单已被处理");
			}

			OrderMember orderMember = orderMemberService.findMemberByKey(orderWork.getOrderId());
			if (!Objects.isNull(orderMember)) {
				if (Objects.equals(orderMember.getReviewStatus(), OrderConsts.ORDER_MEMBER_REVIEW_STATUS_WAIT_PLAT) && Objects
						.equals(orderMember.getReviewResult(), OrderConsts.ORDER_MEMBER_REVIEW_RESULT_DOING)) {
					throw new OmsBaseException("工单需后台延保复审,不可操作");
				}
				boolean reviewSuccess = orderMember.getReviewStatus() == OrderConsts.ORDER_MEMBER_REVIEW_STATUS_PLAT_SUCCESS;
				if (reviewSuccess) {
					throw new OmsBaseException("工单为审核通过的延保订单，无法操作");
				}
			}

			// 存在已上门子流程，不允许改派
			/*List<OrderVisit> orderVisitList = orderVisitService.listByOrderIdAndMasterId(orderWork.getOrderId(), orderWork.getMasterId());
			if (CollectionUtil.isNotNullOrEmpty(orderVisitList)) {
				boolean hasVisit = orderVisitList.stream().anyMatch(e -> Objects.equals(e.getVisitStatus(), OrderVisitStatusConsts.ORDER_VISIT_STATUS_VISIT));
				if (hasVisit) {
					throw new OmsBaseException("存在已上门子流程，不允许改派");
				}
				boolean hasPay = orderVisitList.stream()
						.anyMatch(e -> !Objects.equals(e.getVisitStatus(), OrderVisitStatusConsts.ORDER_VISIT_STATUS_CANCEL)
								&& Objects.equals(e.getPayStatus(), PayConsts.PAY_STATUS_NONE)
								&& (NumberUtil.isNotNullOrZero(e.getOrderPayId())
								|| NumberUtil.isNotNullOrZero(e.getAcceptanceId())));
				if (hasPay) {
					throw new OmsBaseException("存在待支付子流程，不允许改派");
				}
			}*/

			ChangeMasterDTO changeMasterDTO = BeanMapper.map(changeMasterDIO, ChangeMasterDTO.class);
			this.setLogParam(changeMasterDIO, changeMasterDTO);
			zsMasterWorkBService.updateMaster(changeMasterDTO);

			// 返回更新后的工单列表
			WorkListDTO workListDTO = zsMasterWorkBService.getWorkingList(changeMasterDIO.getMasterId());
			WorkListDRO workListDRO = BeanMapper.map(workListDTO, WorkListDRO.class);
			return ResponseDTO.success(workListDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 修改产品，并且重设订单的计价器类
	 *
	 * @param modifyProductDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyProduct(ModifyProductDIO modifyProductDIO) {
		logger.info("[{}] 修改修改订单产品：ModifyProductDIO={}", TAG, JSON.toJSONString(modifyProductDIO));

		try {
			OperatePermissionVO operatePermission = orderWorkOperatePermissionBService
					.getOperatePermission(modifyProductDIO.getOrderId(), modifyProductDIO.getWorkId(), OrderConsts.ORDER_OP_TYPE_MODIFY_PRODUCT);
			if (!operatePermission.getCanOperate()) {
				throw new OmsBaseException(operatePermission.getMsg());
			}
			ModifyProductDTO modifyProductDTO = BeanMapper.map(modifyProductDIO, ModifyProductDTO.class);
			this.setLogParam(modifyProductDIO, modifyProductDTO);

			// 修改产品，有可能修改订单计价器类型，清空，由后台判断是否修改
			modifyProductDTO.setServItemType(null);

			orderWorkModifyProductBService.updateOrderProductByMaster(modifyProductDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(modifyProductDIO.getPlat(),
					modifyProductDIO.getOrderId(), modifyProductDIO.getWorkId(), modifyProductDIO.getMasterId(),
					modifyProductDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);

			// 一口价服务项订单保存历史计价器名称数据
			if (Objects.equals(workDetailDRO.getFinalPrice(),GlobalConsts.YES) ||
					Objects.equals(workDetailDRO.getServItemType(),OrderConsts.SERVICE_ITEM_TYPE_ORDER)){
				List<OrderFinalPriceQuotation> orderFinalPriceQuotations = orderFinalPriceQuotationService.
						listByQuery(OrderFinalPriceQuotationQuery.builder()
								.orderId(workDetail.getOrderId())
								.workId(workDetail.getWorkId())
								.build());
				if (CollectionUtil.isNotEmpty(orderFinalPriceQuotations)){
					OrderFinalPriceQuotation orderFinalPriceQuotation = orderFinalPriceQuotations.get(0);
					Integer productId = modifyProductDIO.getProductId();
					ResponseDTO<List<ProductBaseDRO>> listResponseDTO = productForeignListRemoteService.listBaseDROByQuery(ProductBaseQuery.builder()
							.productId(productId)
							.showType(BaseProductConsts.ERP_SHOW_TYPE)
							.build());
					log.info("productForeignListRemoteService.listBaseDROByQuery 入参:{},出参:{}",productId,listResponseDTO);
					List<ProductBaseDRO> data = listResponseDTO.getData();
					if (CollectionUtil.isNotEmpty(data)){
						orderFinalPriceQuotation.setTariffName(data.get(0).getTariffName());
						orderFinalPriceQuotationService.updateByKey(orderFinalPriceQuotation);
					}
				}
			}

			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 修改产品，并且重设订单的计价器类
	 *
	 * @param modifyProductDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyBrand(ModifyProductDIO modifyProductDIO) {
		logger.info("[{}] 修改修改订单产品品牌：ModifyProductDIO={}", TAG, JSON.toJSONString(modifyProductDIO));

		try {
			ModifyProductDTO modifyProductDTO = BeanMapper.map(modifyProductDIO, ModifyProductDTO.class);
			this.setLogParam(modifyProductDIO, modifyProductDTO);

			orderWorkModifyProductBService.updateOrderProductBrandByMaster(modifyProductDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(modifyProductDIO.getPlat(),
					modifyProductDIO.getOrderId(), modifyProductDIO.getWorkId(), modifyProductDIO.getMasterId(),
					modifyProductDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);

			return ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 修改定金
	 * @param modifyDepositAmountDIO
	 */
	@Override
	public ResponseDTO<Boolean> modifyDepositAmount(ModifyDepositAmountDIO modifyDepositAmountDIO) {
		try {

			ZsUpdatePriceDTO zsUpdatePriceDTO = BeanMapper.map(modifyDepositAmountDIO, ZsUpdatePriceDTO.class);
			this.setLogParam(modifyDepositAmountDIO, zsUpdatePriceDTO);

			zsNormalMasterWorkBService.saveUpdatePriceForEngineer(zsUpdatePriceDTO);
			return ResponseDTO.success();
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 修改订单报价（仅针对计价器类型订单调用，不修改订单的计价器类型）
	 *
	 * @param modifyQuotationDIO
	 */
	@Override
	public ResponseDTO<WorkDetailDRO> modifyOrderQuotation(ModifyQuotationDIO modifyQuotationDIO) {

		logger.info("[{}] 修改计价器订单报价：ModifyQuotationDIO={}", TAG,  JSON.toJSONString(modifyQuotationDIO));
		com.zmn.common.dto2.ResponseDTO responseDTO;
		try {
			OperatePermissionVO operatePermission = orderWorkOperatePermissionBService
					.getOperatePermission(modifyQuotationDIO.getOrderId(), modifyQuotationDIO.getWorkId(), OrderConsts.ORDER_OP_TYPE_MODIFY_QUOTATION);
			if (!operatePermission.getCanOperate()) {
				throw new OmsBaseException(operatePermission.getMsg());
			}
			ModifyQuotationDTO modifyQuotationDTO = BeanMapper.map(modifyQuotationDIO, ModifyQuotationDTO.class);
			this.setLogParam(modifyQuotationDIO, modifyQuotationDTO);
			modifyQuotationDTO.setOperatorId(modifyQuotationDIO.getMasterId().longValue());

			// 计价器订单修改产品，不会变更订单的计价器类型，不需要后台判断
			modifyQuotationDTO.setServItemType(OrderConsts.SERVICE_ITEM_TYPE_FAULT);
			modifyQuotationDTO.setQuotationType(GlobalConsts.OPERATE_USER_TYPE_MASTER);

			// 更新报价
			zsOrderWorkBService.updateOrderQuotation(modifyQuotationDTO);

			// 返回更新后的工单详情
			WorkDetailDTO workDetail = zsMasterWorkBService.getWorkDetailSrcMaster(modifyQuotationDIO.getPlat(),
					modifyQuotationDIO.getOrderId(), modifyQuotationDIO.getWorkId(), modifyQuotationDIO.getMasterId(),
					modifyQuotationDIO.getAgent());
			WorkDetailDRO workDetailDRO = BeanMapper.map(workDetail, WorkDetailDRO.class);
			responseDTO = ResponseDTO.success(workDetailDRO);
		} catch (OmsBaseException e) {
			responseDTO = ResponseDTO.fail(e.getCode(), e.getMessage());
		}

		// 发送费用清单模版消息
		try {
			OrderWork orderWork = orderWorkService.findOrderWorkByKey(modifyQuotationDIO.getOrderId(), modifyQuotationDIO.getWorkId());
			//sendWechatTemplateService.sendQuotationByUpdateTemplate(orderWork);
			sendOrderMessageService.sendDesignatedRuleIdMessage(orderWork.getOrderId(), MessageRuleIdConsts.MESSAGE_GLOBAL_QUOTATION_CONFIRM_NODE_MARK, MessageRuleIdConsts.ZMN_MSG_RULEID_QUOTATION_CONFIRM);

		} catch (Exception e) {
			logger.error(e.getMessage(), e);
		}
		return responseDTO;
	}

	/**
	 * 发送用户报价模板消息
	 *
	 * @param masterWorkDIO
	 */
	@Override
	public ResponseDTO<Boolean> sendQuotationWechatTemplate(MasterWorkDIO masterWorkDIO) {
		OrderWork orderWork = orderWorkService.findOrderWorkByKey(masterWorkDIO.getOrderId(), masterWorkDIO.getWorkId());

		//boolean isSuccess = sendWechatTemplateService.sendQuotationTemplate(orderWork);
		boolean isSuccess = sendOrderMessageService.sendDesignatedRuleIdMessage(orderWork.getOrderId(), MessageRuleIdConsts.MESSAGE_GLOBAL_QUOTATION_NODE_MARK, MessageRuleIdConsts.ZMN_MSG_RULEID_QUOTATION);
		return com.zmn.common.dto2.ResponseDTO.success(isSuccess);
	}

	/**
	 * 检查修改产品
	 *
	 * @param modifyProductDIO
	 */
	@Override
	public ResponseDTO<Boolean> checkUpdateProduct(ModifyProductDIO modifyProductDIO) {
		ModifyProductDTO modifyProductDTO = BeanMapper.map(modifyProductDIO, ModifyProductDTO.class);
		String resultMessage = orderWorkModifyProductBService.checkUpdateProduct(modifyProductDTO);
		if (StringUtil.isBlank(resultMessage)) {
			return ResponseDTO.success(true);
		} else {
			return ResponseDTO.fail(resultMessage);
		}
	}


	/**
	 * 验证完成核销码
	 * @param verifyCompleteCodeDIO
	 * @return
	 */
	@Override
	public ResponseDTO verifyCompleteCode(VerifyCompleteCodeDIO verifyCompleteCodeDIO) {

		logger.info("[{}] 验证完成核销码：VerifyCompleteCodeDIO={}", TAG, JSON.toJSONString(verifyCompleteCodeDIO));

		try {
			zsMasterWorkBService.verifyCompleteCode(verifyCompleteCodeDIO.getOrderId(), verifyCompleteCodeDIO.getWorkId(), verifyCompleteCodeDIO.getCompleteCode());
			return ResponseDTO.success();
		}catch (OmsBaseException omsBaseException) {
			return ResponseDTO.fail(omsBaseException.getMessage());
		}
	}

	/**
	 * 小号延绑
	 * @param XNOBindDIO
	 */
	@Override
	public ResponseDTO<OrderDelayBindDRO> delayBind(XnoBindDIO XNOBindDIO){

		OrderWork orderWork = orderWorkService.findOrderWorkByKey(XNOBindDIO.getOrderId(), XNOBindDIO.getWorkId());
		OrderDetail orderDetail= orderDetailService.findOrderDetailByKey(XNOBindDIO.getOrderId());

		OrderDelayBindDRO orderDelayBindDRO = new OrderDelayBindDRO();
		// 未绑定过不需延绑
		if (orderDetail.getBindStatus() == 0) {
			orderDelayBindDRO.setDelayStatus(GlobalConsts.YES);
			return ResponseDTO.success(orderDelayBindDRO);
		}

		Boolean result = true;
		try{
			List<DelayBindDTO> binds = Lists.newArrayList();

			String telephone = orderDetail.getTelephone();
			ZsXnoBindVO zsXnoBindVO = orderXnoBindService.queryXNO(XNOBindDIO.getMobile(), telephone, orderWork);
			if(zsXnoBindVO != null && zsXnoBindVO.getStatus() == 2){
				DelayBindDTO delayBindDTO = DelayBindDTO.builder().bindId(zsXnoBindVO.getBindId()).delta(OrderConsts.BIND_TIME).build();
				binds.add(delayBindDTO);
			}
			if (StringUtils.isNotBlank(orderDetail.getTelephone2())) {
				String telephone2 = orderDetail.getTelephone2();
				ZsXnoBindVO zsXnoBindVO2 = orderXnoBindService.queryXNO(XNOBindDIO.getMobile(), telephone2, orderWork);
				if(zsXnoBindVO2 != null && zsXnoBindVO2.getStatus() == 2){
					DelayBindDTO delayBindDTO = DelayBindDTO.builder().bindId(zsXnoBindVO2.getBindId()).delta(OrderConsts.BIND_TIME).build();
					binds.add(delayBindDTO);
				}
			}
			if (StringUtils.isNotBlank(orderDetail.getTelephone3())) {
				String telephone3 = orderDetail.getTelephone3();
				ZsXnoBindVO zsXnoBindVO3 = orderXnoBindService.queryXNO(XNOBindDIO.getMobile(), telephone3, orderWork);
				if(zsXnoBindVO3 != null && zsXnoBindVO3.getStatus() == 2){
					DelayBindDTO delayBindDTO = DelayBindDTO.builder().bindId(zsXnoBindVO3.getBindId()).delta(OrderConsts.BIND_TIME).build();
					binds.add(delayBindDTO);
				}
			}

			if(binds.size() != 0){
				result = orderXnoBindService.delayBind(binds);
			}
		} catch (Exception e) {
			log.info("师傅小号延绑接口异常：{}", e.getMessage());
			result = false;
		}

		if(result){
			orderDelayBindDRO.setDelayStatus(GlobalConsts.YES);
		}else {
			orderDelayBindDRO.setDelayStatus(GlobalConsts.NO);
			orderDelayBindDRO.setTelephone(orderDetail.getTelephone());
			orderDelayBindDRO.setTelephone2(orderDetail.getTelephone2());
			orderDelayBindDRO.setTelephone3(orderDetail.getTelephone3());
		}
		return ResponseDTO.success(orderDelayBindDRO);
	}



	/**
	 * @Description 判断是否是延保电器
	 * @Author xiaofei
	 * @Param BaseRequestDIO
	 * @Return ResponseDTO<Boolean>
	 * @Version 1.0
	 * @Date 2020-06-03 18:21
	 */
	@Override
	public ResponseDTO<Boolean> checkExtensionInsuranceAppliances(BaseRequestDIO baseRequestDIO){
		log.info("checkExtensionInsuranceAppliances:orderId:["+baseRequestDIO.getOrderId()+" workId:"+baseRequestDIO.getWorkId()+"]");
		OrderWork orderWork = orderWorkService.findOrderWorkByKey(baseRequestDIO.getOrderId(), baseRequestDIO.getWorkId());
		OrderExtensionDIO orderExtensionDIO = new OrderExtensionDIO();
		orderExtensionDIO.setUserId(orderWork.getUserId());
		orderExtensionDIO.setCategOneId(orderWork.getShowCategOneId());
		orderExtensionDIO.setCategTwoId(orderWork.getShowCategId());
		orderExtensionDIO.setServCategId(orderWork.getServCategId());
		orderExtensionDIO.setPlat(orderWork.getPlat());
		orderExtensionDIO.setOrderType(orderWork.getType());
		com.zmn.common.dto2.ResponseDTO<Boolean> booleanResponseDTO = vasOrderListRemoteService.checkExtensionInsuranceAppliances(orderExtensionDIO);
		return ResponseDTO.success(booleanResponseDTO.getData());
	}

	/**
	 * @Description 根据易碎贴编码获取增值订单信息
	 * @Author xiaofei
	 * @Param String
	 * @Return ResponseDTO<ValueAddedInfoDRO>
	 * @Version 1.0
	 * @Date 2020-06-04 16:31
	 */
	@Override
	public ResponseDTO<ValueAddedInfoDRO> getExtendedWarrantyInfoByCode(AddedValueOrderDIO addedValueOrderDIO) {

		log.info("omsDubboInfo:根据易碎贴编码查询增值单信息:fragileCode:"+addedValueOrderDIO);
		if (StringUtil.isBlank(addedValueOrderDIO.getFragileCode())){
			return ResponseDTO.fail("请填写易碎贴编码");
		}
		ResponseDTO<ExtendedWarrantyDRO> extendedWarrantyInfo = vasOrderListRemoteService.getExtendedWarrantyInfoByCode(addedValueOrderDIO.getFragileCode(), addedValueOrderDIO.getWorkId());
		ValueAddedInfoDRO valueAddedInfoDRO = BeanMapper.map(extendedWarrantyInfo.getData(), ValueAddedInfoDRO.class);
		return ResponseDTO.success(valueAddedInfoDRO);
	}

	/**
	 * @Description 获取根据报价人id获取报价次数(只计算计价器订单)
	 * @Author hgb
	 * @Return ResponseDTO<Integer>
	 * @Date 2020年07月14日17:17:21
	 */
	@Override
	public ResponseDTO<Integer> countMasterFirstQuotation(MasterFirstQuotationDIO masterFirstQuotationDIO) {

		logger.info("获取根据报价人id获取报价次数：countMasterFirstQuotation---{}", JSON.toJSONString(masterFirstQuotationDIO));
		int i = 0;
		try {
			OrderWorkQuery orderWorkQuery = BeanMapper.map(masterFirstQuotationDIO, OrderWorkQuery.class);
			orderWorkQuery.setServItemType(OrderConsts.SERVICE_ITEM_TYPE_FAULT);
			Integer countOrderWork = zsOrderWorkQueryBService.countOrderWorkByQuery(orderWorkQuery);
			i = countOrderWork == null ? 0 : countOrderWork;
		} catch (Exception e) {
			e.printStackTrace();
		}
		return ResponseDTO.success(i);
	}

	@Override
	public ResponseDTO<Boolean> needCompleteCode(Long orderId, Long workId) {
		if (orderId == null || workId == null) {
			return ResponseDTO.fail("工单号不能为空");
		}
		return ResponseDTO.success(zsMasterWorkBService.needCompleteCode(orderId, workId));
	}

	/**
	 * 工单服务完成
	 * @param dio
	 */
	@Override
	public ResponseDTO<Integer> checkServiceComplete(ServiceCompleteDIO dio) {

		log.info("校验工单服务完成入参：ServiceCompleteDIO :{}", JSONObject.toJSONString(dio));

		if (dio.getOrderId() == null || dio.getWorkId() == null) {
			return ResponseDTO.fail("工单号不能为空");
		}
		if (NumberUtil.isNullOrZero(dio.getMasterId())) {
			return ResponseDTO.fail("师傅ID不能为空");
		}
		try {
			// 校验服务完成前置条件
			zsNormalMasterWorkBService.checkServiceComplete(BeanMapper.map(dio, com.zmn.oms.model.dto.work.masterwork.ServiceCompleteDIO.class));

		} catch (OmsBaseException oe) {
			return ResponseDTO.success(GlobalConsts.NO, oe.getMessage());
		} catch (Exception e) {
			logger.error(String.format("[%s]校验工单服务完成异常", dio.getWorkId()), e);
			return ResponseDTO.fail("校验服务完成失败，请稍后重试");
		}
		return ResponseDTO.success(GlobalConsts.YES);
	}

	/**
	 * 工单服务完成
	 * @param dio
	 */
	@Override
	public ResponseDTO<Integer> serviceComplete(ServiceCompleteDIO dio) {

		log.info("工单服务完成入参：ServiceCompleteDIO :{}",JSONObject.toJSONString(dio));

		if (dio.getOrderId() == null || dio.getWorkId() == null) {
			return ResponseDTO.fail("工单号不能为空");
		}
		if (NumberUtil.isNullOrZero(dio.getMasterId())) {
			return ResponseDTO.fail("师傅ID不能为空");
		}
		try {
			// 校验服务完成前置条件
			OrderWork dbOrderWork = zsNormalMasterWorkBService.checkServiceComplete(BeanMapper.map(dio, com.zmn.oms.model.dto.work.masterwork.ServiceCompleteDIO.class));

			{// 智米订单在完成前，需先同步给对方完成状态
				Integer channelId = dbOrderWork.getChannelId();
				if (channelId == null) {
					OrderWork orderWork = orderWorkService.findOrderWorkByKey(dio.getOrderId(), dio.getWorkId());
					if (orderWork == null) {
						throw new OmsBaseException("工单不存在");
					}
					channelId = orderWork.getChannelId();
				}

				if (Objects.equals(ZhimiConsts.CHANNEL_ID, channelId)) {
					ResultDTO resultDTO = zhimiOrderExtendService.check4Complete(dio.getOrderId());
					if (!resultDTO.isStatusBool()) {
						throw new OmsBaseException(resultDTO.getMessage());
					}
				}
			}

			com.zmn.oms.model.dto.work.masterwork.ServiceCompleteDIO serviceCompleteDIO = BeanMapper.map(dio, com.zmn.oms.model.dto.work.masterwork.ServiceCompleteDIO.class);
			// todo fubiao
			logger.info("serviceComplete#getEngineerDetailById 入参 [{}]",dio.getMasterId());
			ResponseDTO<ForeignEngineerDetailInfoDRO> engineerByEngineerId = engineerListRemoteService.getEngineerDetailById(dio.getMasterId());
			logger.info("serviceComplete#getEngineerDetailById 出参 [{}]",JSON.toJSONString(engineerByEngineerId));
			if (engineerByEngineerId.isSuccess()) {
				serviceCompleteDIO.setOperator(engineerByEngineerId.getData().getRealName());
			}
			serviceCompleteDIO.setStatus(OrderStatusConsts.WORK_STATUS_SERVICE_COMPLETE);
			this.setLogParam(dio, serviceCompleteDIO);
			zsMasterWorkBService.serviceComplete(serviceCompleteDIO);

			// 订单自动流转
			workFlowContextBService.asyncAutoFlow(dio.getOrderId(), dio.getWorkId());

			OrderWork orderWork = orderWorkService.findOrderWorkByKeySrcMaster(dio.getOrderId(), dio.getWorkId());

			// 1 待审核  2 审核成功未完成  3 已完成
			Integer resultFlag = 1;
			if (Objects.equals(orderWork.getStatus(), OrderStatusConsts.WORK_STATUS_SERVICE_COMPLETE) && Objects.equals(orderWork.getServiceCompleteReviewStatus(), OrderConsts.REVIEW_STATUS_SUCCESS)) {
				resultFlag = 2;
			} else if (orderWork.getStatus() >= OrderStatusConsts.WORK_STATUS_COMPLETE) {
				resultFlag = 3;
			}

			return ResponseDTO.success(resultFlag);
		} catch (OmsBaseException exception) {
			log.error("【{}】服务完成失败:{}", dio.getWorkId(), exception.getMessage());
			return ResponseDTO.fail(exception.getCode(),exception.getMessage());
		}
	}

	@Override
	public ResponseDTO revertServiceComplete(ServiceCompleteDIO dio) {

		try {
			com.zmn.oms.model.dto.work.masterwork.ServiceCompleteDIO serviceCompleteDIO = BeanMapper.map(dio, com.zmn.oms.model.dto.work.masterwork.ServiceCompleteDIO.class);
			// 重置工单表
			OrderWork updateOrderWork = new OrderWork();
			updateOrderWork.setOrderId(serviceCompleteDIO.getOrderId());
			updateOrderWork.setWorkId(serviceCompleteDIO.getWorkId());
			updateOrderWork.setStatus(OrderStatusConsts.WORK_STATUS_VISIT);
			updateOrderWork.setServiceCompleterId(serviceCompleteDIO.getOperatorId());
			updateOrderWork.setServiceCompleteTime(DateUtil.getNow());
			updateOrderWork.setServiceCompleteReviewStatus(GlobalConsts.NONE);
			updateOrderWork.setUpdater(serviceCompleteDIO.getOperator());
			masterWorkService.updateServiceComplete(updateOrderWork);

			// 更新师傅进行中表
			MasterWorking masterWorking = new MasterWorking();
			masterWorking.setWorkId(serviceCompleteDIO.getWorkId());
			masterWorking.setServiceCompleteReviewStatus(GlobalConsts.NONE);
			masterWorkingService.updateMasterWorking(masterWorking);
		}catch (Exception exception){
			log.error("【{}】服务完成重置报错:{}", dio.getWorkId(), exception.getMessage());
			ResponseDTO.fail("服务完成重置报错失败，请稍后重试");
		}
		return ResponseDTO.success();
	}

	@Override
	public ResponseDTO modifyOrderAttachment(ModifyOrderAttachmentDIO dio) {

		try {

			List<OrderAttachment> orderAttachments = orderAttachmentService.listAttachmentByOrderIdSrcMaster(dio.getOrderId());
			Optional<OrderAttachment> first = orderAttachments.stream().filter(e -> Objects.equals(e.getType(), dio.getType())).findFirst();

			if (first.isPresent()) {
				// 更新图片url
				OrderAttachment orderAttachment = first.get();
				String imgUrl = masterWorkBService.convertUrls(orderAttachment.getSrc(), dio.getImg(), dio.getOpType(), dio.getIndex());
				if(imgUrl.startsWith(",")){
					imgUrl = imgUrl.substring(1);
				}
				orderAttachment.setSrc(imgUrl);
				if (imgUrl.length() == 0) {
					orderAttachmentService.deleteByKey(orderAttachment.getAttachmentId());
				} else {
					orderAttachmentService.updateByKey(orderAttachment);
				}
			} else {
				// 新增
				if (StringUtil.isNotBlank(dio.getImg())) {
					OrderAttachment orderAttachment = BeanMapper.map(dio, OrderAttachment.class);
					orderAttachment.setSrc(dio.getImg());
					orderAttachmentService.insertAttachment(orderAttachment);
				}
			}
		} catch (Exception exception) {
			return ResponseDTO.fail("保存工单附件照片失败，请稍后重试");
		}
		return ResponseDTO.success();
	}

	@Override
	public ResponseDTO modifyOrderDifficultRatio(ModifyOrderDiffcultRatioDIO dio) {
		try {
			OrderExtendDTO dto = BeanMapper.map(dio, OrderExtendDTO.class);
			this.setLogParam(dio, dto);
			orderExtendBService.modifyDifficultId(dto);
		} catch (Exception exception) {
			return ResponseDTO.fail("保存工单难度系数失败，请稍后重试");
		}
		return ResponseDTO.success();
	}

	/**
	 * 描述：主动发送支付模板消息
	 *
	 * @param orderId    订单id
	 * @param workId     工单id
	 * @param payMsgType 支付类型（1为定金待支付，2为完成待支付）
	 * @return
	 */
	@Override
	public ResponseDTO<Boolean> waitPayNoticeById(Long orderId, Long workId, Integer payMsgType) {

		try {
			boolean result = masterWorkBService.sendWaitPayNotice(orderId, workId, payMsgType);
			log.info("orderId :{}, waitPayNoticeById 出参:{}", orderId, result);
			if (result) {
				return ResponseDTO.success();
			} else {
				return ResponseDTO.fail("消息发送失败");
			}
		} catch (OmsBaseException e) {
			log.error("发送支付消息失败:{}",e.getMessage());
			return ResponseDTO.fail(e.getCode(),e.getMessage());
		}
	}

	/**
	 * 描述：主动发送支付模板消息
	 *
	 * @return
	 */
	@Override
	public ResponseDTO<Integer> waitPayNotice(WaitPayDIO waitPayDIO) {
		logger.info("主动发送支付模板消息入参：【{}】", JSON.toJSONString(waitPayDIO));
		try {

			OrderWork orderWork = orderWorkService.findOrderWorkByKey(waitPayDIO.getOrderId(), waitPayDIO.getWorkId());
			if (Objects.isNull(orderWork) || NumberUtil.isNullOrZero(orderWork.getVisitUserId())) {
				OrderExtend orderExtend = orderExtendService.findOrderExtendByOrderId(waitPayDIO.getOrderId());
				if (Objects.isNull(orderExtend) || NumberUtil.isNullOrZero(orderExtend.getWeChatScanUserId())) {
					log.info("sendWaitPayNotice 发送失败--上门用户不存在");
					return ResponseDTO.success(GlobalConsts.NONE);
				}
				orderWork.setVisitUserId(orderExtend.getWeChatScanUserId());
			}

			// 检验用户是否关注
			Boolean isAttentionWechat = checkAttentionWeChat(orderWork);
			if (!isAttentionWechat){
				return ResponseDTO.success(GlobalConsts.NONE);
			}

			// 渠道支付---返回渠道支付标识
			List<PayChannelDRO> listPayChannel = orderPayChannelBService.listPayChannel(orderWork.getPlatWork(), orderWork.getBizModeSource(), orderWork.getChannelId(), orderWork.getServProductGroupId());

			// 是否需要用户支付
			Boolean needUserPay = false;
			if (!ProductConsts.LIST_SPECIAL_SERV_PRODUCT_GROUP.contains(orderWork.getServProductGroupId()) &&
					Objects.equals(orderWork.getPlatWork(), GlobalConsts.PLAT_MARK_ZMN) && NumberUtil.isNotNullOrZero(orderWork.getVisitUserId())) {
				log.info("{}支持用户模版消息支付", orderWork.getWorkId());
				boolean eciticPay = listPayChannel.stream()
						.anyMatch(e -> Objects.equals(e.getPayChannelId(), PayConsts.PAY_CHANNEL_THIRD_ECITIC));
				boolean weixinPay = listPayChannel.stream()
						.anyMatch(e -> Objects.equals(e.getPayChannelId(), PayConsts.PAY_CHANNEL_PLATFORM_WEIXINPAY));
				if (eciticPay || weixinPay) {
					needUserPay = true;// 支持中信或微信支付，才给用户支付
				}
			}

			if (!needUserPay) {
				return ResponseDTO.success(GlobalConsts.NONE);
			}

			boolean result = masterWorkBService.sendWaitPayNotice(waitPayDIO.getOrderId(), waitPayDIO.getWorkId(), orderWork.getVisitUserId(), waitPayDIO.getOrderPayId());
			log.info("orderId :{}, waitPayNoticeById 出参:{}", waitPayDIO.getOrderId(), result);
			if (result) {
				return ResponseDTO.success(GlobalConsts.YES);
			} else {
				return ResponseDTO.success(GlobalConsts.NO);
			}
		} catch (Exception e) {
			return ResponseDTO.fail("发送微信支付消息失败");
		}
	}

	/**
	 * 描述：服务完成待确认模板消息
	 *
	 * @param orderId    订单id
	 * @param workId     工单id
	 * @return
	 */
	@Override
	public ResponseDTO<Boolean> serviceCompleteNoticeById(Long orderId, Long workId) {

		OrderWork orderWork = orderWorkService.findOrderWorkByKey(orderId, workId);
		if (Objects.isNull(orderWork) || NumberUtil.isNullOrZero(orderWork.getVisitUserId())) {
			log.info("sendWaitPayNotice 发送失败--上门用户不存在");
			return ResponseDTO.fail("发送失败--上门用户不存在");
		}
		// 发送待确认消息
		boolean result = messageWeChatTemplateService.sendDesignatedUserWeChatTemplate(orderId, MessageRuleIdConsts.ZMN_MSG_RULEID_SERVICE_COMPLETE_CONFIRM, orderWork.getVisitUserId());
		return ResponseDTO.success(result);
	}

	/**
	 * 审核申请优惠，10-20秒钟随机数后自动优惠
	 *
	 * @param zsDiscountDTO
	 */
	private void addMasterApplyDiscountJob(ZsDiscountDTO zsDiscountDTO) {
		String msg = JSON.toJSONString(zsDiscountDTO);
		Job job = new Job();
		job.setTaskId(TaskConsts.TASK_ID_MASTER_APPLY_DISCOUNT + ":" + zsDiscountDTO.getOrderId());
		job.setParam(TaskManager.SHARD_FIELD, TaskConsts.TASK_ID_MASTER_APPLY_DISCOUNT);
		job.setParam("applyDiscountDIO", msg);
		int second = (int) (10 + Math.random() * (20 - 10 + 1));// 设置10到20秒的随机数
		Date date = DateUtil.addSecond(DateUtil.getNow(), second);
		com.zmn.common.dto.ResultDTO result = taskManager.submitTask(job, -1, DateUtil.dateFormatToString(date, DateUtil.FORMAT_DEFAULT));
		if (!result.getStatusBool()) {
			log.error("#oms#oms_master_apply_discount_job# job submit fail...");
		}
		if (result.getStatusBool()) {
			String redisKey = String.format(RedisKeyConsts.MASTER_APPLY_DISCOUNT_REVIEWING_KEY, String.valueOf(zsDiscountDTO.getOrderId()), zsDiscountDTO.getMasterId());
			redisManager.setex(redisKey, msg, 60 * 60);
		}
	}

	@Override
	public ResponseDTO resetMasterAPPVersion(@NotNull(message = "masterId不能为空") Integer masterId) {

		// 刷新工程师工单列表版本号
		//engineerTouchModifyRemoteService.saveEngineerWorkVersion(masterId, null);

		mqProviderService.sendEngineerWorkVersion(masterId,null);
		return null;
	}

	/**
	 * 更新联系用户时间
	 *
	 * @param contactUserDIO
	 * @return
	 */
	@Override
	public ResponseDTO updateContactUser(ContactUserDIO contactUserDIO) {
		try {
			ContactUserDTO contactUserDTO = BeanMapper.map(contactUserDIO, ContactUserDTO.class);
			this.setLogParam(contactUserDIO, contactUserDTO);
			zsMasterWorkBService.saveContactUserTime(contactUserDTO);
			return ResponseDTO.success();
		} catch (OmsBaseException e) {
			return ResponseDTO.fail(e.getCode(), e.getMessage());
		}
	}

	/**
	 * 描述：跳过上门扫码
	 *
	 * @param baseRequestDIO
	 */
	@Override
	public ResponseDTO skipVisitScan(BaseRequestDIO baseRequestDIO) {
		log.info("{} 跳过上门扫码 ",baseRequestDIO.getOrderId());
		// 更新工单扫码操作状态
		OrderExtend orderExtend = new OrderExtend();
		orderExtend.setExtId(baseRequestDIO.getOrderId());
		orderExtend.setOperateVisitScan(GlobalConsts.NO);
		MasterVisitQrDTO visitQrDTO = BeanMapper.map(baseRequestDIO, MasterVisitQrDTO.class);
		this.setLogParam(baseRequestDIO, visitQrDTO);
		visitQrDTO.setOrderId(baseRequestDIO.getOrderId());
		visitQrDTO.setWorkId(baseRequestDIO.getWorkId());
		visitQrDTO.setOpenId(null);
		masterWorkBService.visitUserQrCode(visitQrDTO);
		orderExtendService.updateOrderExtend(orderExtend);
		return ResponseDTO.success();
	}

	/**
	 * 发送计价器报价次数超限预警短信
	 *
	 * @param quotationWarnMsgDIO
	 * @return
	 */
	@Override
	public ResponseDTO sendQuotationWarnMessage(QuotationWarnMsgDIO quotationWarnMsgDIO) {

		OrderWork orderWork = orderWorkService.findOrderWorkByKey(quotationWarnMsgDIO.getOrderId(), quotationWarnMsgDIO.getWorkId());
		// 发送派单撤回app消息
		Map<String, String> params = Maps.newHashMap();
		params.put("order_id", String.valueOf(quotationWarnMsgDIO.getOrderId()));
		params.put("work_id", String.valueOf(quotationWarnMsgDIO.getWorkId()));
		params.put("biz_type", orderWork.getBizType().toString());
		params.put("count", quotationWarnMsgDIO.getUsedCount().toString());
		params.put("count_surplus", quotationWarnMsgDIO.getSurplusCount().toString());
		messageSendAppService.pushAppMessageInfo(MessageConsts.ZMN_MSG_RULEID_QUOTATION_WARN, JSON.toJSONString(params), orderWork);
		return ResponseDTO.success();
	}

	/**
	 * 发送四位短信验证码
	 *
	 * @param masterCaptchaDIO
	 * @return
	 */
	@Override
	public ResponseDTO sendCaptchaMessage(MasterCaptchaDIO masterCaptchaDIO) {

		Map<String, String> smsMap = new HashMap<>();
		smsMap.put("code", masterCaptchaDIO.getCaptcha());
		messageSendTextService.sendTextMessage(MessageConsts.ZMN_MSG_CAPTCHA, masterCaptchaDIO.getPhone(), smsMap);
		return ResponseDTO.success();
	}

	@Override
	public ResponseDTO completeCleanService(ModifyOrderWorkAttachmentDIO modifyOrderWorkAttachmentDIO) {
		try {
			log.info("完成清洁服务#completeCleanService:{}", JSON.toJSONString(modifyOrderWorkAttachmentDIO));
			masterWorkBService.completeCleanService(modifyOrderWorkAttachmentDIO);
			return ResponseDTO.success();
		}catch (OmsBaseException e){
			log.error("完成清洁服务报错",e);
			return ResponseDTO.fail(e.getMessage());
		}
	}

	/**
	 * 检验用户是否关注
	 * @param orderWork 工单信息
	 */
	private Boolean checkAttentionWeChat(OrderWork orderWork){
		OrderThirdAppBind orderThirdAppBind = messageGetSendInfoService.getOrderWeChatBindInfoForOrderBy(orderWork.getOrderId(), orderWork.getPlatWork());
		if (Objects.isNull(orderThirdAppBind) || StringUtils.isBlank(orderThirdAppBind.getThirdAppId())) {
			log.info("订单号{}，未找到绑定公众号信息", orderWork.getWorkId());
			return false;
		}

		ResponseDTO<Boolean> isAttentionWechat = userThirdListRemoteService.getThirdSubscribeByUserIdAndAppId(orderWork.getVisitUserId(), orderThirdAppBind.getThirdAppId());
		log.info("订单号{},查询用户是否关注公众号,userId:{},appId:{},出参:{}",orderWork.getOrderId(),orderWork.getVisitUserId(),orderThirdAppBind.getThirdAppId(),isAttentionWechat);
		if (isAttentionWechat.isSuccess() && Objects.nonNull(isAttentionWechat.getData())){
			return isAttentionWechat.getData();
		}else {
			log.error("调用getThirdSubscribeByUserIdAndAppId查看用户是否关注公众号接口错误");
			return false;
		}
	}
}
